﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Web.UI.WebControls;
using crm_library.Extenstions;

namespace crm_library.Controls.CompoundControls
{
	public class DateChooser : BaseCompoundControl
	{
		public enum DateChooserLayoutType
		{
			/// <summary>
			/// just render raw controls, unformated.
			/// </summary>
			Simple,

			/// <summary>
			/// render all controls inside a panel.
			/// </summary>
			HorizontalPanel,

			/// <summary>
			/// render all controls inside a panel, where each control has a line break rendered after it.
			/// </summary>
			VerticalPanel,

			/// <summary>
			/// Render all controls horizontally with each control inside its own table cell.
			/// </summary>
			HorizontalTable,

			/// <summary>
			/// Render all controls vertically with each control inside its own table row.
			/// </summary>
			VerticalTable,
		}

		public enum DateChooserRenderFilter
		{
			AllControls,
			LabelOnly,
			ControlsOnly
		}

		public enum StartingValues
		{
			NonSelected,
			Earliest,
			Latest
		}

		private DateTime _from;
		private DateTime _to;

		private DropDownList _year;
		private DropDownList _month;
		private DropDownList _day; 

		public DateChooserLayoutType Layout {get; set;}
		public DateChooserRenderFilter RenderFilter { get; set; }
		public StartingValues StartingValue { get; set; }

		public DateChooser(DateTime earliest, DateTime latest, StartingValues startingValue)
		{
			StartingValue = startingValue;

			_from = new DateTime(earliest.Year, earliest.Month, earliest.Day);
			_to = new DateTime(latest.Year, latest.Month, latest.Day).AddDays(1);

			_year = new DropDownList();
			_month = new DropDownList();
			_day = new DropDownList();
			SetUpDates();
		}

		private void SetUpDates()
		{
			var years = new List<int>();
			var months = new List<int>();
			var days = new List<int>();

			if(_from < _to)
			{
				while(_from < _to)
				{
					years.AddUnique(_from.Year);
					months.AddUnique(_from.Month);
					days.AddUnique(_from.Day);

					_from = _from.AddDays(1);
				}
			}

			_year.Items.AddRange(years.Select(year => new ListItem(year.ToString())).ToArray());
			_month.Items.AddRange(months.Select(month => new ListItem(month.ToString())).ToArray());
			_day.Items.AddRange(days.Select(day => new ListItem(day.ToString())).ToArray());

			switch (StartingValue)
			{
				default:
				case StartingValues.NonSelected:
					_year.Items.Insert(0, new ListItem("", _from.Year.ToString() ));
					_month.Items.Insert(0, new ListItem("", _from.Month.ToString()));
					_day.Items.Insert(0, new ListItem("", _from.Day.ToString()));
					break;
				case StartingValues.Earliest:
					_year.SelectedIndex = 0;
					_month.SelectedIndex = 0;
					_day.SelectedIndex = 0;
					break;
				case StartingValues.Latest:
					_year.SelectedIndex = _year.Items.Count - 1;
					_month.SelectedIndex = _month.Items.Count - 1;
					_day.SelectedIndex = _day.Items.Count - 1;
					break;
			}


			


		}

		public override string Value
		{
			get
			{
				const string format = "{0, 4:0000}-{1, 2:00}-{2, 2:00}"; //YYYY-MM-DD
				return string.Format(format, _year.SelectedValue, _month.SelectedValue, _day.SelectedValue);
			}
			set
			{
				DateTime temp;
				if(DateTime.TryParse(value, out temp))
				{
					_year.SelectByValue(temp.Year);
					_month.SelectByValue(temp.Month);
					_day.SelectByValue(temp.Day);
				}
			}
		}

		private string _ID = "";
		public override string ID
		{
			get
			{
				if (_ID == null) _ID = "";
				return _ID;
			}
			set
			{
				_ID = value;
				_year.ID = value + "_year";
				_month.ID = value + "_month";
				_day.ID = value + "_day";
			}
		}

		private System.Web.UI.ClientIDMode _clientIDMode;
		public override System.Web.UI.ClientIDMode ClientIDMode
		{
			get
			{
				return _clientIDMode;
			}
			set
			{
				_clientIDMode = value;
				_year.ClientIDMode = value;
				_month.ClientIDMode = value;
				_day.ClientIDMode = value;
			}
		}

		

		protected override void CreateChildControls()
		{
			var pane = new Panel
							{
								ID = _ID + "_panel",
								ClientIDMode = _clientIDMode
							};
			var tbl = new Table
							{
								ID = _ID + "_table",
								ClientIDMode = _clientIDMode
							};

			switch (Layout)
			{
				default:
				case DateChooserLayoutType.Simple:
					if (RenderFilter.IncludesLabel()) this.Controls.Add(Lbl);
					if (RenderFilter.IncludesControl())
						{
							this.Controls.Add(_year);
							this.Controls.Add(_month);
							this.Controls.Add(_day);
						}
					break;
				case DateChooserLayoutType.HorizontalPanel:
					if (RenderFilter.IncludesLabel()) pane.Controls.Add(Lbl);
					if (RenderFilter.IncludesControl())
						{
							pane.Controls.Add(_year);
							pane.Controls.Add(_month);
							pane.Controls.Add(_day);
						}
					this.Controls.Add(pane);
					break;
				case DateChooserLayoutType.VerticalPanel:
					if (RenderFilter.IncludesLabel())
					{
						pane.Controls.Add(Lbl);
						pane.Controls.Add(LineBreak);
					}
					if (RenderFilter.IncludesControl())
					{
						pane.Controls.Add(_year);
						pane.Controls.Add(LineBreak);
						pane.Controls.Add(_month);
						pane.Controls.Add(LineBreak);
						pane.Controls.Add(_day);
						pane.Controls.Add(LineBreak);
					}
					this.Controls.Add(pane);
					break;
				case DateChooserLayoutType.HorizontalTable:
					var row = new TableRow();
					if (RenderFilter.IncludesLabel())
					{
						var headerCell = new TableHeaderCell();
						headerCell.Controls.Add(Lbl);
						row.Cells.Add(headerCell);
					}
					if (RenderFilter.IncludesControl())
					{
						var yearCell = new TableCell();
						yearCell.Controls.Add(_year);
						row.Cells.Add(yearCell);

						var monthCell = new TableCell();
						monthCell.Controls.Add(_month);
						row.Cells.Add(monthCell);

						var dayCell = new TableCell();
						dayCell.Controls.Add(_day);
						row.Cells.Add(dayCell);
						
					}
					tbl.Rows.Add(row);
					this.Controls.Add(tbl);
					break;
				case DateChooserLayoutType.VerticalTable:
					if (RenderFilter.IncludesLabel())
					{
						var header = new TableHeaderRow{ TableSection = TableRowSection.TableHeader };
						var headerCell = new TableHeaderCell();
						headerCell.Controls.Add(Lbl);
						header.Cells.Add(headerCell);
						tbl.Rows.Add(header);
					}
					if (RenderFilter.IncludesControl())
					{
						var yearRow = new TableRow();
						var yearCell= new TableCell();
						yearCell.Controls.Add(_year);
						yearRow.Cells.Add(yearCell);
						tbl.Rows.Add(yearRow);

						var monthRow = new TableRow();
						var monthCell = new TableCell();
						monthCell.Controls.Add(_month);
						monthRow.Cells.Add(monthCell);
						tbl.Rows.Add(monthRow);

						var dayRow = new TableRow();
						var dayCell = new TableCell();
						dayCell.Controls.Add(_day);
						dayRow.Cells.Add(dayCell);
						tbl.Rows.Add(dayRow);
					}
					this.Controls.Add(tbl);
					break;
			}



			
		}
		private static Literal LineBreak { get { return new Literal { Text = "<br />" }; } }

	}

	public static class RenderFilterExtensions
	{
		public static bool IncludesLabel(this DateChooser.DateChooserRenderFilter filter)
		{
			return (filter != DateChooser.DateChooserRenderFilter.ControlsOnly);
		}

		public static bool IncludesControl(this DateChooser.DateChooserRenderFilter filter)
		{
			return (filter != DateChooser.DateChooserRenderFilter.LabelOnly);
		}
	}
}

